package controller;

import java.io.IOException;
import java.io.PrintWriter;
import java.text.SimpleDateFormat;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import com.google.appengine.api.xmpp.*;

import model.DAO;
import model.EventInfo;
import model.EventUser;
import model.EventPlus;
import model.EventLike;
import model.EventMsg;
import model.UserProfile;

import org.codehaus.jackson.map.JsonMappingException;
import org.codehaus.jackson.map.ObjectMapper;
import org.codehaus.jackson.*;

public class ChatServlet extends HttpServlet{

	//private ChatDAO dao = new ChatDAO();
	private DAO dao = new DAO();
	ObjectMapper mapper = new ObjectMapper();
	//XMPP
	XMPPService xmpp = XMPPServiceFactory.getXMPPService();
	
	private void joinChat(long eid, String uid)
	{
		if(!dao.checkEventUser(eid, uid))
			return;
		
		String jid = dao.getUserJid(uid);
		EventUser eu  = new EventUser(eid, uid);
		eu.setJid(jid);		
		dao.ofy().put(eu);
		dao.updateEventUseCount(eid, true);
	}

	private void plusEvent(long eid, String uid)
	{
		dao.ofy().put(new EventPlus(eid, uid));
		dao.incEventPlusCount(eid);
	}

	private void likeEvent(long eid, String uid)
	{
		dao.ofy().put(new EventLike(eid, uid));
		dao.incEventLikeCount(eid);
	}

	private void sendMsg(long eid, String uid, String msg)
	{
		dao.ofy().put(new EventMsg(eid, uid, msg));
	}

	private void leaveChat(long eid, String uid)
	{
		dao.deleteEventUser(eid, uid);
		dao.updateEventUseCount(eid, false);
	}

	private String getEventUser(long eid) throws JsonGenerationException, JsonMappingException, IOException
	{
		List<UserProfile> list = dao.getEventUser(eid);
		return mapper.writeValueAsString(list);		
	}

	private String getEventMsg(long eid) throws JsonGenerationException, JsonMappingException, IOException
	{
		List<EventMsg> list = dao.getEventMsg(eid);
		return mapper.writeValueAsString(list);		
	}
	
	private String getEventPlus(long eid) throws JsonGenerationException, JsonMappingException, IOException
	{
		List<UserProfile> list = dao.getEventPlus(eid);
		return mapper.writeValueAsString(list);		
	}

	private String getEventLike(long eid) throws JsonGenerationException, JsonMappingException, IOException
	{
		List<UserProfile> list = dao.getEventLike(eid);
		return mapper.writeValueAsString(list);		
	}
	
	private void sendXmppMessage(String info, long eid) {
		
		List <String> list = dao.getEventJidList(eid);
		
		JID jid;
		for(String s:list) {			
			String jid_str = s + "@cad117.cs.nthu.edu.tw/Smack";
			jid = new JID(jid_str);
		
			System.out.println("Send to JID = " + jid.toString());
	        Message msg = new MessageBuilder()
	            .withRecipientJids(jid)
	            .withBody(info)
	            .build();
			
			// boolean messageSent = false;	     
		     SendResponse status = xmpp.sendMessage(msg);
		     System.out.println(status.getStatusMap().get(jid));
		     //messageSent = (status.getStatusMap().get(jid) == SendResponse.Status.SUCCESS);
		}
	}
	
	private String makeXMPPMsg(String uid, String action) throws JsonGenerationException, JsonMappingException, IOException 
	{
		UserProfile up = dao.getUserProfileById(uid);
		String fbid = String.valueOf(up.getFbid());
		String username = up.getName();
		
		Map<String,String> nameStruct = new HashMap<String,String>();
		nameStruct.put("name", username);
		nameStruct.put("fbid", fbid);
		nameStruct.put("action", action);
	
		return mapper.writeValueAsString(nameStruct);	
	}
	
	@Override
	protected void doGet(HttpServletRequest req, HttpServletResponse resp)
			throws ServletException, IOException {

		long eid = 0;
		if(req.getParameter("eid") != null)
			eid = Long.parseLong(req.getParameter("eid"));
		
		String type = req.getParameter("type");
		String result = "No Type!!";
				
		if(type!=null){			
			if(eid!=0){
				if(type.equals("use")) {
					result = getEventUser(eid);
				} else if(type.equals("plus")) {
					result = getEventPlus(eid);
				} else if(type.equals("like")) {
					result = getEventLike(eid);
				} else if(type.equals("message")) {
					result = getEventMsg(eid);
				} else if(type.equals("send")) {
					String uid = req.getParameter("uid");
					String info = makeXMPPMsg(uid, "join");
					System.out.println(info);
					sendXmppMessage(info, eid);
				}
				
			}
		}
		
		resp.setContentType("application/json;charset=UTF-8");
        PrintWriter out = resp.getWriter();        
		out.println(result);
	}	
	
	@Override
	protected void doPost(HttpServletRequest req, HttpServletResponse resp)
			throws ServletException, IOException {
				
		//String result = "No Action!!";
		String action = req.getParameter("action");
		long eid = 0; 
		String uid;
		String msg;
		
		if(req.getParameter("eid")!=null)
			eid = Long.parseLong(req.getParameter("eid"));
		uid = req.getParameter("uid");
		msg = req.getParameter("msg");
		
		if(action.equals("join")) {
			joinChat(eid, uid);
		}			
		else if(action.equals("plus")) {		
			plusEvent(eid, uid);
		}
		else if(action.equals("like")) {
			likeEvent(eid, uid);
		}
		else if(action.equals("send")) {
			sendMsg(eid, uid, msg);
		}
		else if(action.equals("leave")) {
			leaveChat(eid, uid);
		}
	
		String info;
		if(action!=null) {
			info = makeXMPPMsg(uid, action);
			System.out.println(info);
			sendXmppMessage(info, eid);
		}
		
		//resp.setContentType("text/plain");
		//resp.getOutputStream().write("OK!".getBytes());
	}

}
